#include <iomanip>
#include "DateTime.h"
#include "sstream"

namespace zg_util{

    std::string DateTime::CurDateStr(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d",t.tm_year+1900);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mon+1);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mday);
            return std::string(tmp);
    }
    std::string DateTime::CurDateTimeStr(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d-%02d-%02d %02d:%02d:%02d",t.tm_year+1900,t.tm_mon+1,t.tm_mday,t.tm_hour,t.tm_min,t.tm_sec);
            return std::string(tmp);
    }
    std::string DateTime::CurDateStrSub(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d",t.tm_year+1900);
            p=tmp+strlen(tmp);
            sprintf(p,"-0%02d",t.tm_mon+1);
            p=tmp+strlen(tmp);
            sprintf(p,"-0%02d",t.tm_mday);
            return std::string(tmp);
    }

    std::string DateTime::CurDateHourStr(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d",t.tm_year+1900);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mon+1);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mday);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_hour);
            return std::string(tmp);
    }

    std::string DateTime::CurDateHourBeforeSecStr(int secs){
            time_t timep;
            struct tm t;
            time(&timep);
            timep-=secs;
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d",t.tm_year+1900);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mon+1);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mday);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_hour);
            return std::string(tmp);
    }
    std::string DateTime::CurMysqlDateBeforeSecStr(int secs){
            time_t timep;
            struct tm t;
            time(&timep);
            timep-=secs;
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d",t.tm_year+1900);
            p=tmp+strlen(tmp);
            sprintf(p,"-%02d",t.tm_mon+1);
            p=tmp+strlen(tmp);
            sprintf(p,"-%02d",t.tm_mday);
            return std::string(tmp);
    };
    std::string DateTime::CurMysqlDateTimeBeforeSecStr(int secs){
            time_t timep;
            struct tm t;
            time(&timep);
            timep-=secs;
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d-%02d-%02d %02d:%02d:%02d",t.tm_year+1900,t.tm_mon+1,t.tm_mday,t.tm_hour,t.tm_min,t.tm_sec);
            return std::string(tmp);
    };
    std::string DateTime::CurTimeStr(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%02d:",t.tm_hour);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d:",t.tm_min);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_sec);
            return std::string(tmp);
    }
    std::string DateTime::CurHourStr(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[16]={0};
            char *p=tmp;
            sprintf(p,"%02d",t.tm_hour);
            return std::string(tmp);
    }
    std::string DateTime::CurDayStr(){
            time_t timep;
            struct tm t;
            time(&timep);
            localtime_r(&timep,&t);
            char tmp[16]={0};
            char *p=tmp;
            sprintf(p,"%02d",t.tm_mday);
            return std::string(tmp);
    }

    int DateTime::ParseMysqltime(const std::string &mysql_time,int &year,int& mon,int& day,int &hour,int &min,int &sec){
            if(mysql_time.size()!=19)
                    return -1;
            year=String::StringToInt<int>(mysql_time.substr(0,4));
            mon=String::StringToInt<int>(mysql_time.substr(5,2));
            day=String::StringToInt<int>(mysql_time.substr(8,2));
            hour=String::StringToInt<int>(mysql_time.substr(11,2));
            min=String::StringToInt<int>(mysql_time.substr(14,2));
            sec=String::StringToInt<int>(mysql_time.substr(17,2));
            return 0;

    }
    int DateTime::ParseDateStr(const std::string& str,int& year,int& mon,int& day,int& hour){
            if(str.size()!=10)
                    return -1;
            std::stringstream ss;
            ss << str.substr(0, 4);
            ss >> year;
            ss.clear();
            ss << str.substr(4, 2);
            ss >> mon;
            ss.clear();
            ss << str.substr(6, 2);
            ss >> day;
            ss.clear();
            ss << str.substr(8, 2);
            ss >> hour;
            ss.clear();
            return 0;
    }
    std::string DateTime::FetchDateStr(const int year,const int mon,const int day,const int hour) {
            char buf[1024]={0};
            char *p=buf;
            sprintf(p,"%d",year);
            p=buf+strlen(buf);
            sprintf(p,"%02d",mon);
            p=buf+strlen(buf);
            sprintf(p,"%02d",day);
            p=buf+strlen(buf);
            sprintf(p,"%02d",hour);
            return string(buf);
    }
    std::string DateTime::DateStrBefore(int days){
            time_t timep;
            struct tm t;
            time(&timep);
            timep-=3600*24*days;
            localtime_r(&timep,&t);
            char tmp[32]={0};
            char *p=tmp;
            sprintf(p,"%d",t.tm_year+1900);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mon+1);
            p=tmp+strlen(tmp);
            sprintf(p,"%02d",t.tm_mday);
            return std::string(tmp);
    }
    long int DateTime::CurUsec(){
            struct timeval tv;
            gettimeofday(&tv,NULL);
            return tv.tv_usec;
    }
//#if __cplusplus >= 201103L
//    template<typename T>
//    T DateTime::MkTimePoint(int year,int mon,int day,int hour,int min,int sec){
//            std::tm tm1;
//            tm1.tm_year=year-1900;
//            tm1.tm_mon=mon-1;
//            tm1.tm_mday=day;
//            tm1.tm_hour=hour;
//            tm1.tm_min=min;
//            tm1.tm_sec=sec;
//
//            auto time_t1=std::mktime(&tm1);
//            T t_p;
//            t_p+=std::chrono::seconds(time_t1);
//            return t_p;
//    }
//    template<typename T>
//    T DateTime::MkTimePoint(std::tm &&t) {
//            auto time_t1=std::mktime(&t);
//            T t_p;
//            t_p+=std::chrono::seconds(time_t1);
//            return t_p;
//    }

//    template<typename T>
//    T DateTime::MkTimePoint(std::tm &t) {
//            auto time_t1=std::mktime(&t);
//            T t_p;
//            t_p+=std::chrono::seconds(time_t1);
//            return t_p;
//    }
//    template<typename CharT,typename T >
//    T DateTime::MkTimePoint(const string& date_time_str, const CharT *fmt) {
//            std::stringstream ss(date_time_str);
//            std::tm tm1;
//            ss>>std::get_time(&tm1,fmt);
//            return MkTimePoint(tm1);
//    }
//#endif

}